/* 
 * Advanced Foundation Classes
 * Copyright (C) 2000/2004  Fabio Rotondo - Andrea Galimberti
 *  
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *  
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *  
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 */

#include "easygui.h"
#include "widgets.h"

EasyGUI * egui;

static const char class_name[] = "EasyGUI";

static char * afc_easygui_internal_resolve_image_name ( EasyGUI * easygui, const char * filename );
static int afc_easygui_int_dnd_target_del ( void * data );

// {{{ afc_easygui_new ()
/*
@node afc_easygui_new

	         NAME: afc_easygui_new     - Initializes a new afc_easygui instance.

	     SYNOPSIS: EasyGUI * afc_easygui_new ()

	  DESCRIPTION: This function initializes a new afc_easygui instance.

	        INPUT: - NONE

	      RESULTS: a valid inizialized afc_easygui structure. NULL in case of errors.

	     SEE ALSO: - afc_easygui_delete()

@endnode
*/
EasyGUI * afc_easygui_new ( )
{
TRY ( EasyGUI * )

	F_IN()

	EasyGUI * easygui = ( EasyGUI * ) afc_malloc ( sizeof ( EasyGUI ) );

	if ( easygui == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "EasyGUI", NULL );

	easygui->magic = AFC_EASYGUI_MAGIC;

	if ( ( easygui->parser = afc_cmd_parser_new () ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "parser", NULL );
	if ( ( easygui->commands = afc_dynamic_class_master_new () ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "commands", NULL );
	if ( ( easygui->def_params = afc_malloc ( sizeof ( EasyGUIDefaultParams ) ) ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "def_params", NULL );
	if ( ( easygui->contexts = afc_dictionary_new () ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "contexts", NULL );
	if ( ( easygui->dnd_targets = afc_dictionary_new () ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "dnd targets", NULL );

	afc_dictionary_set_clear_func ( easygui->contexts, afc_easygui_context_del );
	afc_dictionary_set_clear_func ( easygui->dnd_targets, afc_easygui_int_dnd_target_del );

	// ----------- Internal Data Stuff
	if ( ( easygui->int_data = afc_malloc ( sizeof ( EasyGUIInternalData ) ) ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "int_data", NULL );
	if ( ( easygui->int_data->delimiters = afc_string_new ( 10 ) ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "delimiters", NULL );

	afc_string_copy ( easygui->int_data->delimiters, "|", ALL );

	if ( ( easygui->int_data->local = g_module_open ( NULL, 0 ) ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "local", NULL );
	if ( ( easygui->int_data->snode = afc_stringnode_new () ) == NULL ) RAISE_FAST_RC ( AFC_ERR_NO_MEMORY, "snode", NULL );
	// ----------------------------------------------------------------------------------------------

	egui = easygui;

	RETURN ( easygui );
EXCEPT
	afc_easygui_delete ( easygui );

FINALLY

ENDTRY
}
// }}}
// {{{ afc_easygui_delete ( egui )
/*
@node afc_easygui_delete

	         NAME: afc_easygui_delete ( easygui )  - Disposes a valid easygui instance.

	     SYNOPSIS: int afc_easygui_delete ( EasyGUI * easygui)

	  DESCRIPTION: This function frees an already alloc'd afc_easygui structure.

	        INPUT: - easygui  - Pointer to a valid afc_easygui class.

	      RESULTS: should be AFC_ERR_NO_ERROR

	        NOTES: - this method calls: afc_easygui_clear()

	     SEE ALSO: - afc_easygui_new()
	               - afc_easygui_clear()

*/
int _afc_easygui_delete ( EasyGUI * easygui ) 
{
	int afc_res; 

	F_IN()

	if ( ( afc_res = afc_easygui_clear ( easygui ) ) != AFC_ERR_NO_ERROR ) return ( afc_res );

	if ( easygui->parser ) 		afc_cmd_parser_delete ( easygui->parser );

	if ( easygui->contexts ) 	afc_dictionary_delete ( easygui->contexts );
	if ( easygui->int_data )
	{
		if ( easygui->int_data->delimiters )	afc_string_delete ( easygui->int_data->delimiters );
		if ( easygui->int_data->local ) 	g_module_close ( easygui->int_data->local );
		if ( easygui->int_data->snode )		afc_stringnode_delete ( easygui->int_data->snode );

		afc_free ( easygui->int_data );	
	}

	if ( easygui->commands ) afc_dynamic_class_master_delete ( easygui->commands );
	if ( easygui->def_params ) afc_free ( easygui->def_params );

	// XXX CHECK: is this the right method to remove an IconFactory from memory?
	if ( easygui->icons )	gtk_icon_factory_remove_default ( easygui->icons );

	// XXX easygui->tips are automagically freed?
	afc_free ( easygui );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_clear ( egui )
/*
@node afc_easygui_clear

	         NAME: afc_easygui_clear ( easygui )  - Clears all stored data

	     SYNOPSIS  int afc_easygui_clear ( EasyGUI * easygui)

	  DESCRIPTION: Use this function to clear all stored data in the current easygui instance.

	        INPUT: - easygui    - Pointer to a valid afc_easygui instance.

	      RESULTS: should be AFC_ERR_NO_ERROR
	              
	     SEE ALSO: - afc_easygui_delete()
	               
@endnode

*/
int afc_easygui_clear ( EasyGUI * easygui ) 
{
	// EasyGUIContext * ectx = NULL;

	F_IN()

	if ( easygui == NULL ) return ( AFC_ERR_NULL_POINTER );
 
	if ( easygui->magic != AFC_EASYGUI_MAGIC ) return ( AFC_ERR_INVALID_POINTER );
	if ( easygui->parser ) afc_cmd_parser_clear ( easygui->parser );

	if ( easygui->commands ) afc_dynamic_class_master_clear ( easygui->commands );
	if ( easygui->contexts ) afc_dictionary_clear ( easygui->contexts );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_init ( egui )  *************
/*
@node afc_easygui_init

@endnode
*/
int afc_easygui_init ( EasyGUI * easygui )
{
	int afc_res = AFC_ERR_NO_ERROR;

	F_IN()

	gtk_init ( NULL, NULL );

	// easygui->curr_context = afc_easygui_add_context ( easygui, AFC_EASYGUI_CONTEXT_MAIN );

	if ( ( afc_res = afc_easygui_internal_init_widgets ( easygui ) ) == AFC_ERR_NO_ERROR ) 
	{
		afc_res = afc_cmd_parser_add_commands ( easygui->parser, easygui->commands );
	}

	if ( ( easygui->icons = gtk_icon_factory_new () ) == NULL ) 
	{
		afc_easygui_delete ( easygui );
		return ( AFC_LOG_FAST_INFO ( AFC_ERR_NO_MEMORY, "icon_factory" ) );
	}

	if ( ( easygui->tips = gtk_tooltips_new () ) == NULL ) 
	{
		afc_easygui_delete ( easygui );
		return ( AFC_LOG_FAST_INFO ( AFC_ERR_NO_MEMORY, "tooltips" ) );
	}

	gtk_icon_factory_add_default ( easygui->icons );

	return ( afc_res );
}
// }}}
// {{{ afc_easygui_main ( egui )  *************
/*
@node afc_easygui_main

@endnode
*/
int afc_easygui_main ( EasyGUI * easygui )
{
	F_IN ()

	gtk_main ();

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_preload_icon ( egui, fname )
/*
@node afc_easygui_preload_icon
	       NAME:	afc_easygui_preload_icon ( easygui, filename )	 - Attemps to load an icon from disk (or cache)

	   SYNOPSIS: 	GtkWidget * afc_easygui_preload_icon ( EasyGUI * easygui, const char * filename );

	DESCRIPTION: 	Attemps to read a new icon in memory cache for future using from /filename/.
			If the /filename/ cannot be found, an error is returned.

	     INPUTS:	- egui 		- Pointer to a valid EasyGUI class.
			- filename	- Name of the image to load

	    RESULTS:	- Should be AFC_ERR_NO_ERROR

	   SEE ALSO:	- afc_easygui_load_icon()
@endnode
*/
int afc_easygui_preload_icon ( EasyGUI * easygui, const char * filename )
{
	GdkPixbuf * pixbuf;
	GtkIconSet * icon_set;

	F_IN()

	if ( filename == NULL ) return ( AFC_ERR_NO_ERROR );
	if ( filename[0]=='@' ) return ( AFC_ERR_NO_ERROR );

	if ( ( icon_set = gtk_icon_factory_lookup_default ( filename ) ) == NULL )
	{
		if ( ( pixbuf = gdk_pixbuf_new_from_file ( filename, NULL ) ) == NULL )
		{
			_afc_dprintf ( "%s: ERROR LOADING IMAGE: %s\n", __FUNCTION__, filename );

			return ( AFC_EASYGUI_ERR_NO_PIXMAP );	
		}

		icon_set = gtk_icon_set_new_from_pixbuf ( pixbuf );
		
		gtk_icon_factory_add ( easygui->icons, filename, icon_set );

		gtk_icon_set_unref ( icon_set );
		gdk_pixbuf_unref ( pixbuf );
	}

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_load_icon ( egui, filename, size )
/*
@node afc_easygui_load_icon
	       NAME:	afc_easygui_load_icon ( easygui, filename, size )	 - Creates a new icon from file

	   SYNOPSIS: 	GtkWidget * afc_easygui_load_icon ( EasyGUI * easygui, const char * filename, int size );

	DESCRIPTION: 	Creates a GtkImage by loading an image icon from /filename/.
			The image is then stored in the internal GtkIconFactory
			Loads an image icon from /filename/ and puts it in the icons GtkIconFactory.
			If /filename/ starts with a '@' char, then the icon will be searched in the internal
			icon set and not from a file in the file system.
			If the icon is already present, nothing is loaded from disk.

	     INPUTS:	- egui 		- Pointer to a valid EasyGUI class.
			- filename	- Name of the image to load
			- size		- Size of the image. Size can be one of the GtkIconSize
					  values:
		
						+ GTK_ICON_SIZE_INVALID
						+ GTK_ICON_SIZE_MENU
						+ GTK_ICON_SIZE_SMALL_TOOLBAR
  						+ GTK_ICON_SIZE_LARGE_TOOLBAR
  						+ GTK_ICON_SIZE_BUTTON
  						+ GTK_ICON_SIZE_DND
  						+ GTK_ICON_SIZE_DIALOG

	    RESULTS:	- a newly created GtkImage of the given size 

	   SEE ALSO:	- afc_easygui_preload_icon()
@endnode
*/
GtkWidget * afc_easygui_load_icon ( EasyGUI * easygui, const char * filename, int size )
{
	GtkWidget * w;
	char * fname;

	F_IN()

	if ( ( fname = afc_easygui_internal_resolve_image_name ( easygui, filename ) ) == NULL )
		return ( NULL );

	w = gtk_image_new_from_stock ( fname, size );

	if ( fname != filename ) afc_string_delete ( fname );

	return ( w );
}
// }}}
// {{{ afc_easygui_get_icon ( egui, icon, filename, size ) ***********
int afc_easygui_get_icon ( EasyGUI * easygui, GtkWidget * icon, const char * filename, int size )
{
	char * fname;
	GtkIconSet * icon_set;

	F_IN()

	if ( ( fname = afc_easygui_internal_resolve_image_name ( easygui, filename ) ) == NULL )
		return ( AFC_ERR_NO_ERROR );	// FIXME: should I return an error here?

	if ( ( icon_set = gtk_icon_factory_lookup_default ( fname ) ) != NULL )
		gtk_image_set_from_icon_set ( GTK_IMAGE( icon ), icon_set, size );

	if ( fname != filename ) afc_string_delete ( fname );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_set_tip ( egui, widg, tip, long_tip ) **********
/*
	DESCRIPTION: 	sets the Tooltip of the provided GtkWidget /widget/.

	     INPUTS:	- egui 		- Pointer to a valid EasyGUI class.
			- widget	- Widget to assign tip to.
			- tip		- Normal Tooltip
			- long_tip	- Tip with a longer help text
		
	    RESULTS:	- AFC_ERR_NO_ERROR
	
*/
int afc_easygui_set_tip ( EasyGUI * easygui, GtkWidget * widget, const char * tip, const char * long_tip )
{
	F_IN()

	if ( ( tip == NULL ) && ( long_tip == NULL ) ) return ( AFC_ERR_NO_ERROR );

	gtk_tooltips_set_tip ( easygui->tips, widget, tip, long_tip );

	F_OUT()

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_set_tags ( egui, first_tag, ... ) *********
int _afc_easygui_set_tags ( EasyGUI * easygui, int first_tag, ... )
{
	va_list args;
	void * val;
	unsigned int tag;

	F_IN()

	va_start ( args, first_tag );
	tag = first_tag;

	while ( tag != AFC_TAG_END )
	{
		val = va_arg ( args, void * );

		afc_easygui_set_tag ( easygui, tag, val );

		tag = va_arg ( args, int );
	}

	va_end ( args );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_set_tag ( egui, tag, val ) ********
int afc_easygui_set_tag ( EasyGUI * easygui, int tag, void * val )
{
	F_IN()

	switch ( tag )
	{
		case AFC_EASYGUI_TAG_DELIMITERS:
			afc_string_copy ( easygui->int_data->delimiters, ( char * ) val, ALL );			
			break;

		case AFC_EASYGUI_TAG_ESCAPE_CHAR:
			afc_stringnode_set_tags ( easygui->int_data->snode, AFC_STRINGNODE_TAG_ESCAPE_CHAR, val, AFC_TAG_END );
			break;

/*
		case AFC_EASYGUI_TAG_USER_DATA:
			easygui->curr_context->userdata = val;
			break;
*/
	}	

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_add_context ( egui, context_name ) *******
EasyGUIContext * afc_easygui_add_context ( EasyGUI * easygui, char * context_name )
{
	EasyGUIContext * c;

	F_IN()

	// FIXME: some error checking would be nice ;-)

	c = afc_easygui_context_new ( easygui, context_name );
	afc_dictionary_set ( easygui->contexts, c->name, c);

	easygui->curr_context = c;

	return ( c );
}
// }}}

int afc_easygui_add_dnd_target ( EasyGUI * egui, const char * name, int flags, int info )
{
TRY ( int )

	EasyGUIDNDTargetItem * ti = NULL;

	if ( ( ti = afc_malloc ( sizeof ( EasyGUIDNDTargetItem ) ) ) == NULL ) RAISE_FAST ( AFC_ERR_NO_MEMORY, "target item" );
	if ( ( ti->name = afc_string_dup ( name ) ) == NULL ) RAISE_FAST ( AFC_ERR_NO_MEMORY, "target name" );
	if ( ( afc_dictionary_set ( egui->dnd_targets, name, ti ) ) != AFC_ERR_NO_ERROR ) RAISE_FAST ( AFC_ERR_NO_MEMORY, "target add" );

	egui->dnd_targets_changed = TRUE;

	RETURN ( AFC_NO_ERR );
EXCEPT
	if ( ti )
	{
		afc_string_delete ( ti->name );
		afc_free ( ti );
	}

	RETURN ( AFC_ERR_NO_MEMORY );

FINALLY

ENDTRY
}


// ===========================================================================================================
// INTERNAL FUNCTIONS
// ===========================================================================================================

// {{{ afc_easygui_context_set_menu ( context, menu ) *********
int afc_easygui_context_set_menu ( EasyGUIContext * context, GtkWidget * menu )
{
	char * name = context->egui->def_params->name;

	F_IN()

	if ( name == NULL ) return ( AFC_ERR_NO_ERROR );

	afc_dictionary_set ( context->menus, name, menu );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_internal_add_widget ( egui, w, dc )
/*
@node afc_easygui_internal_add_widget

@endnode
*/
int afc_easygui_internal_add_widget ( EasyGUIContext * context, GtkWidget * w, DynamicClass * dc )
{
	afc_dynamic_class_execute ( context->curr_container->dc , "add", w, AFC_DYNAMIC_CLASS_ARG_END );

	afc_easygui_widget_register ( context, w, dc );

	return ( AFC_ERR_NO_ERROR );
}
// }}}
// {{{ afc_easygui_internal_resolve_image_name ( egui, filename )
static char * afc_easygui_internal_resolve_image_name ( EasyGUI * easygui, const char * filename )
{
	char * fname;

	if ( filename == NULL ) return ( NULL );

	if ( afc_easygui_preload_icon ( easygui, filename ) != AFC_ERR_NO_ERROR )
		return ( NULL );	

	if ( filename[0]=='@' )
	{
		fname = afc_string_new ( strlen ( filename ) + 4 );
		afc_string_make ( fname, "gtk-%s", filename + 1 );
	} else 
		fname = ( char * ) filename;

	return ( fname );
}
// }}}
static int afc_easygui_int_dnd_target_del ( void * data )
{
	EasyGUIDNDTargetItem * ti = data;

	if ( ti == NULL ) return ( AFC_NO_ERR );

	afc_string_delete ( ti->name );
	afc_free ( ti );

	return ( AFC_NO_ERR );
}

/**********
 TEST AREA
***********/

#ifdef TEST_CLASS
// {{{ TEST CLASS

NodeMaster * elenco = NULL;
int dummy ( DynamicClass * dc, EasyGUIContext * context )
{
	//NodeMaster * albero = ( NodeMaster * ) afc_easygui_get_userdata ( ( EasyGUI * ) data );
	void * g = NULL;
	int k = 0;

	//fprintf ( stdout, "Hello world! - widget name: %s - event: %s\n", wname, event_name );

	if ( afc_nodemaster_len ( extra_params ) > 0 ) {
		g = ( void * ) afc_nodemaster_first ( extra_params );
		for ( k = 0; k < afc_nodemaster_len ( extra_params ); k++ ) {
			printf ( "param: %x\n", ( int ) g );
			g = ( void * ) afc_nodemaster_next ( extra_params );
		}
	}

	//afc_easygui_widget_set_attrs ( data, "clist", "nome_lista", AFC_EASYGUI_ARG_NODEMASTER, albero, AFC_TAG_END );

	return ( 0 );
}

int rbtoggle ( EasyGUI * eg, char * wname, char * event_name, NodeMaster * extra_params )
{
	EasyGUIWidgetData * ew = afc_easygui_widget_get_by_name ( eg, wname );
	EasyGUIWidgetData * elab = afc_easygui_widget_get_by_name ( eg, "l1" );
	GtkWidget * w = ew->gtk_handle;
	GtkWidget * lab = elab->gtk_handle;

	if ( GTK_TOGGLE_BUTTON ( w )->active )
		gtk_label_set_text ( GTK_LABEL ( lab ), "first button DOWN" );
	else
		gtk_label_set_text ( GTK_LABEL ( lab ), "first button UP" );

	return ( 0 );
}


NodeMaster * dammi_elenco ( EasyGUI * eg )
{
	return elenco;
}

#ifdef DONT_WORK
NodeMaster * dammi_albero ( EasyGUI * eg )
{
	EasyGUITreeItem * ti = NULL;
	EasyGUITreeItem * ti2 = NULL;
	/* retrieve whatever we have stored in EasyGUI's userdata field */
	NodeMaster * albero = ( NodeMaster * ) afc_easygui_get_userdata ( eg );

	/* we instantiate a tree item */
	ti = afc_easygui_tree_item_new ( AFC_EASYGUI_TREE_ITEM_ITEM, "/First Item", NULL );
	/* and we add it to the root tree */
	afc_nodemaster_add ( albero, ti, AFC_NODEMASTER_ADD_TAIL );

	/* second item */
	ti = afc_easygui_tree_item_new ( AFC_EASYGUI_TREE_ITEM_BRANCH, "/Second Item", NULL );
	/* we add it to the root tree the same as before */
	afc_nodemaster_add ( albero, ti, AFC_NODEMASTER_ADD_TAIL );

		/* first subitem */
		ti2 = afc_easygui_tree_item_new ( AFC_EASYGUI_TREE_ITEM_ITEM, "/Second Item/First sub item", NULL );
		/* we add it to the subtree */
		afc_easygui_tree_item_add_subitem ( ti, ti2 ); 

		/* second subitem */
		ti2 = afc_easygui_tree_item_new ( AFC_EASYGUI_TREE_ITEM_ITEM, "/Second Item/Second sub item", NULL );
		afc_easygui_tree_item_add_subitem ( ti, ti2 );

	/* third item:  we have returned to the root tree */
	ti = afc_easygui_tree_item_new ( AFC_EASYGUI_TREE_ITEM_ITEM, "/Third Item", NULL );
	afc_nodemaster_add ( albero, ti, AFC_NODEMASTER_ADD_TAIL );

	return albero;
}
#endif



int main ( int argc, char * argv[] )
{
	AFC * afc = afc_new (); 
	EasyGUI * easygui = afc_easygui_new ( afc );
	int afc_res = 0;
	char * temp = NULL;
	#ifdef DONT_WORK
		EasyGUITreeItem * ti = NULL;
	#endif
	NodeMaster * albero = NULL;

	elenco = afc_nodemaster_new ( afc );
	albero = afc_nodemaster_new ( afc );


	if ( easygui == NULL ) 
	{
	  fprintf ( stderr, "Init of class EasyGUI failed.\n" );
	  return ( 1 );
	}

	afc_easygui_init ( easygui );

	afc_easygui_set_gui ( easygui,
"(window titolo)"
"(rows border=15"
"	(button b1 ciccio)"
"	(label l1 etichetta)"
"	(button b2 TEXT=\"floppy\" ICON=\"3floppy_mount.xpm\")"
"	(cols"
"		(label l2 \"Insert Text:\")"
"		(entry testo 5)"
"	)"
"	(combo combobox null primo secondo terzo 4 5 sei)"
"	(scrolledwindow ALWAYS AUTOMATIC"
"		(rows"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"			(checkbutton NULL Hello!3)"
"		)"
"	)"
")" );
/*
(rows
	(menu main_menu
		/File NULL NULL <Branch>
		/File/Open NULL dummy <Item>
		/File/Other NULL NULL <Branch>
		/File/Other/Touch NULL NULL <Item>
		/Edit NULL NULL <Branch>
		/Edit/Cut NULL NULL <CheckItem>
		/Edit/Paste NULL NULL <Branch>
		/Edit/Paste/First NULL NULL <RadioItem>
		/Edit/Paste/Second NULL NULL /Edit/Paste/First
		/Help NULL NULL <LastBranch>
		\"/Help/Nothing to help\" NULL NULL <Item>
	)
 (eqcols
	(eqrows
	 (radiobutton rb1 A \"primo radiob del gruppo A\" rbtoggle)
	 (radiobutton rb2 A \"secondo rb gruppo A\")
	)
	(eqrows
	 (label l1 etichetta)
	 (label l2 seconda-etichetta)
	)
 )
 (eqcols
	(button b1 pulsante dummy)
	(button b2 TEXT=floppy ICON=3floppy_mount.xpm)
 )
 (checkbutton cb1 Hello!)
 (cols
	(label l_testo \"inserire testo\")
	(entry testo 5)
 )
 (combo combobox null primo secondo terzo 4 5 sei)
 (eqcols
	(scrolledwindow ALWAYS AUTOMATIC
	 (cols
	  (eqrows
	   (checkbutton NULL \"Testo molto lungo per vedere lo scorrimento orizzontale 1\")
	   (checkbutton NULL Hello!2)
	   (checkbutton NULL Hello!3)
	   (checkbutton NULL Hello!4)
	   (checkbutton NULL Hello!5)
	   (checkbutton NULL Hello!6)
	   (checkbutton NULL Hello!7)
	   (checkbutton NULL Hello!8)
	   (checkbutton NULL Hello!9)
	   (checkbutton NULL Hello!10)
	   (checkbutton NULL Hello!11)
	  )
	  (eqrows
	   (button NULL button1)
	   (button NULL button2)
	   (button NULL button3)
	   (button NULL button4)
	   (button NULL button5)
	   (button NULL button6)
	   (button NULL button7)
	   (button NULL button8)
	   (button NULL button9)
	   (button NULL button10)
	   (button NULL button11)
	  )
	 )
	) #fine della scrolledwindow
 )
 (eqcols
	 (image img_name AceKingCards.xpm)
	 (scale s_nome horz 15 0 100 1 10 true top 0)
	 (clist nome_lista 2 30 dummy NULL SHOWTITLES TITLEDATA WIDTHDATA JUSTIFYDATA NMDATA dammi_elenco)
 )
)");
*/

/*

	       Object -Qty
	        100 100
	        < |
	        Potato 123
	        Onion|AceKingCards.xpm  2
	        Computer 1
	        |3floppy_mount.xpm 12
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
	        \"last row\" 1
*/

	afc_nodemaster_add ( elenco, strdup ( "Object" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "-Qty" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "100" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "100" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "<" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "|" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "Potato" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "123" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "Onion|AceKingCards.xpm" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "2" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "Computer" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "|3floppy_mount.xpm" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "12" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "last row" ), AFC_NODEMASTER_ADD_HERE );
	afc_nodemaster_add ( elenco, strdup ( "1" ), AFC_NODEMASTER_ADD_HERE );

	/* userdata can be anything the user wants to be passed to every callback.
	   In this case we set it equal to the "albero" NodeMaster. */
	afc_easygui_set_userdata ( easygui, albero );

	if ( ( afc_res = afc_easygui_show ( easygui ) ) != AFC_ERR_NO_ERROR ) {
		fprintf ( stderr, "res: %x\n", afc_res );
	}
	else afc_easygui_main ( easygui );

	afc_easygui_delete ( easygui );

	temp = ( char * ) afc_nodemaster_first ( elenco );
	while ( temp != NULL ) {
		afc_free ( temp );
		temp = ( char * ) afc_nodemaster_next ( elenco );
	}
	afc_nodemaster_delete ( elenco );

	#ifdef DONT_WORK
	/* free all the tree starting from the root tree */
	ti = ( EasyGUITreeItem * ) afc_nodemaster_first ( albero );
	while ( ti != NULL ) {
		/* this function is recursive: all children of "ti" will be freed automatically */
		afc_easygui_tree_item_delete ( ti );
		ti = ( EasyGUITreeItem * ) afc_nodemaster_next ( albero );
	}
	#endif
	afc_nodemaster_delete ( albero );


	afc_delete ( afc );

	return ( 0 ); 
}
// }}}
#endif
